home *** CD-ROM | disk | FTP | other *** search
- /*****************************************************************
-
- Program: < ADSP Chat >
- File: < Main.c >
-
- Written by Pete Helm, Scott Kuechle
- of <Apple Macintosh Developer Technical Support>
-
- modified by Scott Kuechle
- 10/92 SRK Converted from Pascal to C
- 8/94 SRK Modified to use a queue of parameter
- blocks.
-
- Copyright © 1992, 1994 Apple Computer, Inc.
- All rights reserved.
-
- *****************************************************************/
-
-
- /*****************************************************************/
- /* I N C L U D E S
- /*****************************************************************/
-
- #include "ADSP Chat.h"
-
- /*****************************************************************/
- /* G L O B A L V A R I A B L E D E C L A R A T I O N S
- /*****************************************************************/
-
- DialogPtr myDialog;
-
- Boolean gHasWaitNextEvent,gInBackground,gGrowRect,gStopped,gStopRect,gGoRect,gHasSystem7;
- Boolean gMoofEntityFilter;
-
- MenuHandle ZoneMenu,ObjectMenu,TypeMenu;
- short LastZoneMenuChoice,LastTypeMenuChoice,LastObjectMenuChoice;
- SysEnvRec gMac;
- short gMenuItem;
-
- /*****************************************************************/
- /*
- /* E X T E R N A L S
- /*
- /*****************************************************************/
-
-
- extern myFillRoundRectAnimationRtn (Rect r, PatPtr pat);
- extern void connectToPeer();
- extern void removeADSP();
- extern void initializeADSP();
- extern removeMyName();
- extern void ADSPLoop();
- extern OSErr InitAppleTalk();
- extern Boolean ATPZoneRequest (MenuHandle zoneMenu);
- extern LookupNames (MenuHandle lookupMenu,Boolean doObjects);
- extern GetZones();
- extern GetOurZone();
- extern void writeOutgoing(DSPPBPtr dspPBPtr,
- short ccbRefNum,
- Ptr dataPtr,
- short reqCount);
- extern void removeConnectionEnd();
- extern void removeADSPBuffers();
-
- extern Str255 gZoneString,gTypeStr,gObjStr;
- extern Boolean gConnectionWasJustMade;
- extern TRCCB gMyCCB; /* our ccb */
- extern QHdr gAvailQueue,gReadQueue,gDoneQueue;
- extern short gCCBRefNum; /* ccb reference number returned by adsp on a dspInit */
- extern Ptr outgoingDataBuffer;
- extern DSPPBPtr GetQElement(QHdrPtr qHdrPtr);
-
-
- #pragma segment Main
-
- // *****************************************************************
- // * CopyPstr
- // *
- // * copies a pascal string
- // *****************************************************************
- void CopyPstr(Ptr pSource, Ptr pDest)
- {
- BlockMove(pSource, pDest, pSource[0]+1);
- }
-
- // *****************************************************************
- // * PStrCat
- // *
- // * appends pascal string sourceStr, to pascal string destinationStr.
- // * Overflow is checked, and the copy halts if the destination
- // * string is filled.
- // *****************************************************************
- void PStrCat(Ptr sourceStr, Ptr destinationStr)
- {
- unsigned int srcIndex, dstIndex;
- unsigned int bytesToCopy;
-
- srcIndex = 1;
- dstIndex = destinationStr[0] + 1;
- bytesToCopy = sourceStr[0];
-
- while(bytesToCopy > 0 && dstIndex < 255)
- {
- destinationStr[dstIndex] = sourceStr[srcIndex];
- dstIndex++;
- srcIndex++;
- bytesToCopy--;
- }
- destinationStr[0] = dstIndex - 1;
- }
-
- // *****************************************************************
- // * DoActivate
- // *
- // * This is called when a window is activated or deactivated.
- // * In Sample, the Window Manager's handling of activate and
- // * deactivate events is sufficient. Other applications may have
- // * TextEdit records, controls, lists, etc., to activate/deactivate.
- // *****************************************************************
- void DoActivate (WindowPtr window, Boolean becomingActive)
- {
- #pragma unused (window,becomingActive)
-
- } /*DoActivate*/
-
-
- // *****************************************************************
- // * ShowError
- // *
- // * Our routine for displaying an error message in a dialog box.
- // *****************************************************************
- void ShowError(short index)
- {
- short itemHit;
-
-
- switch (index)
- {
- case atalkErr:
- ParamText("\perror loading AppleTalk drivers!","\p","\p","\p");
- break;
- case memErr:
- ParamText("\pmemory error.","\p","\p","\p");
- break;
- case menuErr:
- ParamText("\perror initializing menus.","\p","\p","\p");
- break;
- case nbpErr:
- ParamText("\pCouldn't register our name on the network (duplicate already exists).","\p","\p","\p");
- break;
- case noTargetErr:
- ParamText("\pTarget not found.","\p","\p","\p");
- break;
- case noConnErr:
- ParamText("\pNo connection has been made.","\p","\p","\p");
- break;
- case writeNotDoneErr:
- ParamText("\pPrevious write has not completed yet.","\p","\p","\p");
- break;
- case badROMsErr:
- ParamText("\pYour machine does not have at least 128K ROMs.","\p","\p","\p");
- break;
- case heapErr:
- ParamText("\pNot enough heap space.","\p","\p","\p");
- break;
- case noMemErr:
- ParamText("\pNot enough memory available for our application.","\p","\p","\p");
- break;
- case DrvrErr:
- ParamText("\pFatal Device Manager error.","\p","\p","\p");
- break;
- case ListenErr:
- ParamText("\pCould not setup connection listener.","\p","\p","\p");
- break;
- case dspInitErr:
- ParamText("\pADSP Initialization failed.","\p","\p","\p");
- break;
- case dspOpenErr:
- ParamText("\pAttempt to open connection failed.","\p","\p","\p");
- break;
- case dspRemoveErr:
- ParamText("\pError returned while eliminating the connection end.","\p","\p","\p");
- break;
-
- default:
- ParamText("\pdefault error displayed here.","\p","\p","\p");
- break;
-
- }
-
- itemHit = Alert(rErrorDialog, nil);
-
- }
-
- // *****************************************************************
- // * FatalError
- // *
- // * This is called when we detect that we cannot operate in the
- // * current environment.
- // *****************************************************************
- void FatalError(error)
- short error;
- {
-
- ShowError(error);
- ExitToShell();
- }
-
- // *****************************************************************
- // * IsAppWindow
- // *
- // * Tells us whether or not a window is an application window
- // *
- // *****************************************************************
- Boolean IsAppWindow(window)
- WindowPtr window;
- {
- short windowKind;
-
- if ( window == nil )
- return false;
- else { /* application windows have windowKinds >= userKind (8) or dialogKind (2) */
- windowKind = ((WindowPeek) window)->windowKind;
- return (windowKind >= userKind) || (windowKind == dialogKind);
- }
- } /* IsAppWindow */
-
- // *****************************************************************
- // * DialogEditing
- // *
- // * handles the standard editing operations (cut, copy, paste)
- // * for our dialog.
- // *****************************************************************
- void DialogEditing (short menuItem)
- {
- /* handles Edit menu */
-
- DialogPeek dp;
- short ignore;
- long evenBiggerIgnore;
-
- dp = (DialogPeek)myDialog;
-
- switch(menuItem)
- {
- case iCut:
- evenBiggerIgnore = ZeroScrap(); /* you really shouldn't ignore this error. see TESample for details */
- TECut(dp->textH);
- ignore = TEToScrap; /* you really shouldn't ignore this error. see TESample for details */
- break;
- case iCopy:
- evenBiggerIgnore = ZeroScrap(); /* you really shouldn't ignore this error. see TESample for details */
- TECopy(dp->textH);
- ignore = TEToScrap; /* you really shouldn't ignore this error. see TESample for details */
- break;
- case iPaste:
- /* you really shouldn't ignore this either. */
- /* one should be checking the length of the incoming scrap to see if it */
- /* will fit in our remaining text edit space. but since we have a weenine 255 */
- /* char dialog text edit item in any case we'll blow it off...see TESample for */
- /* details on "doing the right thing" */
- ignore = TEFromScrap;
- TEPaste(dp->textH);
- break;
- case iClear:
- TEDelete(dp->textH);
- }
- }
-
-
- // *****************************************************************
- // * IsDAWindow
- // *
- // * Check if a window belongs to a desk accessory.
- // *****************************************************************
- Boolean IsDAWindow(WindowPtr window)
- {
-
- if (window == nil)
- return false;
- else /* DA windows have negative windowKinds */
- return((((WindowPeek)window)->windowKind < 0) ? true : false);
- } /*IsDAWindow*/
-
-
- // *****************************************************************
- // * DoCloseWindow
- // *
- // * Close a window. This handles only desk accessory windows because we do not
- // * allow our window to be closed. TESample provides an example of how to handle
- // * the closing of application windows.
- // *****************************************************************
- void DoCloseWindow (WindowPtr window)
- {
- /* Close a window. This handles only desk accessory windows because we do not*/
- /* allow our window to be closed. TESample provides an example of how to handle*/
- /* the closing of application windows.*/
-
-
- if (IsDAWindow(window))
- CloseDeskAcc(((WindowPeek)window)->windowKind);
- } /*DoCloseWindow*/
-
-
- // *****************************************************************
- // * HiliteConnectButton
- // *
- // * sets our connect button to the desired state (active or inactive)
- // *****************************************************************
- void HiliteConnectButton (short mode)
- {
- Rect r;
- short kind;
- Handle h;
-
- GetDItem(myDialog, kConnectButtonID, &kind, &h, &r);
- HiliteControl((ControlHandle)h, mode);
- }
-
- // *****************************************************************
- // * outlinePopUpMenus
- // *
- // * this is a group routine for drawing the popup menu outlines
- // * compleat with drop shadow. the menu title is draw to the left
- // * of the popUp item itself by this routine.
- // *****************************************************************
- void outlinePopUpMenus (WindowPtr whichWindow, Rect r, Str255 itemString)
- {
-
-
- FrameRect(&r);
- MoveTo(r.left + 2, r.bottom);
- LineTo(r.right, r.bottom);
- MoveTo(r.right, r.bottom);
- LineTo(r.right, r.top + 2);
- InsetRect(&r, 1, 1);
- EraseRect(&r);
- InsetRect(&r, -1, -1);
- MoveTo(r.left + 5, r.top + 11);
- TextFont(geneva);
- TextSize(9);
- DrawString(itemString);
- drawPopUpTri(whichWindow, r);
-
- }
-
-
-
-
- // *****************************************************************
- // * UpdateUserItems
- // *
- // * update procedure for the user items in our dialog.
- // *****************************************************************
- pascal void UpdateUserItems (WindowPtr whichWindow,
- short theItem)
- {
- GrafPtr savedPort;
- Rect r;
- short kind;
- Handle h;
-
- GetPort(&savedPort);
- SetPort(whichWindow);
- GetDItem(whichWindow, theItem, &kind, &h, &r);
- switch(theItem)
- {
- case kzoneItemID:
- outlinePopUpMenus(whichWindow, r, gZoneString);
- break;
-
- case ktypeItemID:
- outlinePopUpMenus(whichWindow, r, gTypeStr);
- break;
-
- case kobjectItemID:
- outlinePopUpMenus(whichWindow, r, gObjStr);
- break;
-
- case kRemoteMacsTimeBorderID:
- UpdateItemBorder(theItem, r);
- break;
-
- case kIncomingMessageBorderID:
- UpdateItemBorder(theItem, r);
- break;
-
- case kConnectStatusBorder:
- UpdateItemBorder(theItem, r);
- break;
-
- case kPopupBorderID:
- UpdateItemBorder(theItem, r);
- break;
-
- }
-
- SetPort(savedPort);
- }
-
-
- // *****************************************************************
- // * DoModeless
- // *
- // * this handles mouse clicks inside our main dialog
- // *****************************************************************
- void DoModeless (DialogPtr whichDialog, short whichItem)
- {
- Rect r;
- short kind;
- Handle h;
- MenuHandle allPurposeMenu;
- long menuResult;
- Point pt;
-
-
- if (whichDialog == myDialog)
- {
- GetDItem(whichDialog, whichItem, &kind, &h, &r);
- switch(whichItem)
- {
- case kQuitButtonID:
- Terminate();
- break;
- case kzoneItemID:
- pt.v = r.top;
- pt.h = r.left + 1;
- LocalToGlobal(&pt);
- SetCursor(*(GetCursor(watchCursor)));
- allPurposeMenu = NewMenu(ZoneMenuID, "");
- InsertMenu(allPurposeMenu, -1);
- GetZones(allPurposeMenu);
-
- InitCursor();
- menuResult = PopUpMenuSelect(allPurposeMenu, pt.v, pt.h, 1);
- if (menuResult != 0)
- {
- GetItem(allPurposeMenu, LoWord(menuResult), gZoneString);
- gMenuItem = LoWord(menuResult);
- CopyPstr("\p", gObjStr);
- InvalRect(&r);
- }
- InitCursor();
- DeleteMenu(ZoneMenuID);
- DisposeMenu(allPurposeMenu);
- break;
- case ktypeItemID:
- if (gMoofEntityFilter == false)
- {
- pt.v = r.top - 2;
- pt.h = r.left + 1;
- LocalToGlobal(&pt);
- allPurposeMenu = NewMenu(TypeMenuID, "");
- InsertMenu(allPurposeMenu, -1);
- SetCursor(*(GetCursor(watchCursor)));
- LookupNames(allPurposeMenu, false);
- InitCursor();
- menuResult = PopUpMenuSelect(allPurposeMenu, pt.v, pt.h, 1);
- if (menuResult != 0)
- {
- GetItem(allPurposeMenu, LoWord(menuResult), gTypeStr);
- if (strcmp(gTypeStr,"Moof") == 0)
- HiliteConnectButton(0);
- else
- HiliteConnectButton(255);
- gMenuItem = LoWord(menuResult);
- InvalRect(&r);
- }
-
- DeleteMenu(TypeMenuID);
- DisposeMenu(allPurposeMenu);
- }
- else
- SysBeep(1);
- break;
- case kobjectItemID:
- pt.v = r.top - 2;
- pt.h = r.left + 1;
- LocalToGlobal(&pt);
- allPurposeMenu = NewMenu(ObjectMenuID, "");
- InsertMenu(allPurposeMenu, -1);
- SetCursor(*(GetCursor(watchCursor)));
- LookupNames(allPurposeMenu, true);
- InitCursor();
- menuResult = PopUpMenuSelect(allPurposeMenu, pt.v, pt.h, 1);
- if (menuResult != 0)
- {
- GetItem(allPurposeMenu, LoWord(menuResult), gObjStr);
- gMenuItem = LoWord(menuResult);
- InvalRect(&r);
- }
-
-
- DeleteMenu(ObjectMenuID);
- DisposeMenu(allPurposeMenu);
- break;
- case kConnectButtonID: /* connect button */
- connectToPeer();
- break;
- case kMoofFilterCheckBox:
- if (gMoofEntityFilter == false)
- {
- SetCtlValue((ControlHandle)h,1);
- gMoofEntityFilter = true;
- CopyPstr("\pMoof", gTypeStr);
- HiliteConnectButton(0);
- }
- else
- {
- SetCtlValue((ControlHandle)h,0);
- gMoofEntityFilter = false;
- CopyPstr("\p", gTypeStr);
- if (gMyCCB.state == sClosed)
- HiliteConnectButton(255);
-
- }
-
- gObjStr[0] = 0;
- InvalRect(&myDialog->portRect);
-
- break; /* iMoofFilter */
-
-
- } /* of case */
- }
- }
-
- // *****************************************************************
- // * setEachUserItem
- // *
- // * sets the update routine for our dialogs user items
- // *****************************************************************
- void setEachUserItem (short item)
- {
- Rect r;
- short kind;
- Handle h;
-
- GetDItem(myDialog, item, &kind, &h, &r);
- SetDItem(myDialog, item, userItem, (Handle)UpdateUserItems, &r);
- }
-
-
- // *****************************************************************
- // * DoMenuCommand
- // *
- // *This is called when an item is chosen from the menu bar (after calling
- // * MenuSelect or MenuKey). It performs the right operation for each command.
- // * It is good to have both the result of MenuSelect and MenuKey go to
- // * one routine like this to keep everything organized.
- // *****************************************************************
- void DoMenuCommand (long menuResult)
- {
- short menuID; /*the resource ID of the selected menu*/
- short menuItem; /*the item number of the selected menu*/
- short itemHit;
- Str255 daName;
- short daRefNum;
- Boolean handledByDA;
-
-
- menuID = HiWord(menuResult); /* use built-ins (for efficiency)...*/
- menuItem = LoWord(menuResult); /*to get menu item number and menu number*/
- switch (menuID)
- {
- case mApple:
- switch(menuItem)
- {
- case iAbout: /*bring up alert for About*/
- itemHit = Alert(rAboutDialog, nil);
- break;
- default:
- /*all non-About items in this menu are DAs*/
- GetItem(GetMHandle(mApple), menuItem, daName);
- daRefNum = OpenDeskAcc(daName);
- break;
- }
- break;
- case mFile:
- switch(menuItem)
- {
- case iClose:
- DoCloseWindow(FrontWindow());
- break;
- case iQuit:
- Terminate();
- break;
- }
- break;
- case mEdit: /*call SystemEdit for DA editing & MultiFinder*/
- {
- if (IsDAWindow(FrontWindow()))
- handledByDA = SystemEdit(menuItem - 1);
- else
- DialogEditing(menuItem);
- }
- break;
- }
-
- HiliteMenu(0); /*unhighlight what MenuSelect (or MenuKey) hilited*/
-
- } /*DoMenuCommand*/
-
-
- // *****************************************************************
- // * AdjustMenus
- // *
- // * Enable and disable menus based on the current state.
- // * The user can only select enabled menu items. We set up all the menu items
- // * before calling MenuSelect or MenuKey, since these are the only times that
- // * a menu item can be selected. Note that MenuSelect is also the only time
- // * the user will see menu items. This approach to deciding what enable
- // * disable state a menu item has the advantage of concentrating all the decision-
- // * making in one routine, as opposed to being spread throughout the application.
- // * Other application designs may take a different approach that is just as valid.
- // *****************************************************************
- void AdjustMenus()
- {
- WindowPtr window;
- MenuHandle menu;
-
-
- window = FrontWindow();
-
- menu = GetMHandle(mFile);
- if (IsDAWindow(window)) /*we can allow desk accessories to be closed from the menu*/
- EnableItem(menu, iClose);
- else
- DisableItem(menu, iClose); /*but not our traffic light window*/
-
- menu = GetMHandle(mEdit);
- if (IsDAWindow(window))
- { /*a desk accessory might need the undo item */
- EnableItem(menu, iUndo);
- EnableItem(menu, iCut);
- EnableItem(menu, iCopy);
- EnableItem(menu, iPaste);
- EnableItem(menu, iClear);
- }
- else
- { /* but we do not support undo!!! */
- DisableItem(menu, iUndo);
- EnableItem(menu, iCut);
- EnableItem(menu, iCopy);
- EnableItem(menu, iPaste);
- EnableItem(menu, iClear);
- }
-
- } /*AdjustMenus*/
-
- // *****************************************************************
- // * DisplayCurrentStatus
- // *
- // * updates our connection status string.
- // *****************************************************************
- void DisplayCurrentStatus(Ptr displayStr)
- {
- Rect r;
- short kind;
- Handle h;
-
- Str255 current;
-
- GetDItem(myDialog, kConnectionStatusString, &kind, &h, &r);
- GetIText(h,¤t);
- if (IUCompString(current,displayStr) != 0)
- SetIText(h, displayStr);
-
- }
-
-
-
- // *****************************************************************
- // * DisposeQueueMemory
- // *
- // * deallocate the memory we used for our error queue
- // *****************************************************************
- void DisposeQueueMemory(QHdrPtr qHdrPtr)
- {
- QElemPtr QElem;
- OSErr err;
-
- /* if free queue has any items, dispose of them */
- while (qHdrPtr->qHead != nil)
- {
- QElem = qHdrPtr->qHead;
- err = Dequeue(QElem,qHdrPtr);
- DisposePtr((Ptr)QElem);
- }
- }
-
-
- // *****************************************************************
- // * Terminate
- // *
- // * if we need to quit the program, we remove the connection
- // * end (if any), deallocate any memory we used, remove our
- // * nbp name from the network and exit.
- // *****************************************************************
- void Terminate()
- {
- /* did we establish a connection end? */
- if (gCCBRefNum != 0)
- /* do a dspRemove to close the connection end */
- removeConnectionEnd(gCCBRefNum);
-
- /* deallocate the memory we used for our adsp buffers */
- removeADSPBuffers();
- /* remove our nbp name "moof" */
- removeMyName();
-
- /* dispose of memory we allocated
- for our queues */
- DisposeQueueMemory(&gAvailQueue);
- DisposeQueueMemory(&gDoneQueue);
- DisposeQueueMemory(&gReadQueue);
-
- ExitToShell();
- }
-
- // *****************************************************************
- // * Exit
- // *
- // * this routine is called for fatal control call errors. We exit
- // * the program in this situation.
- // *****************************************************************
- void Exit(short message)
- {
- ShowError(message);
- Terminate();
- }
-
- // *****************************************************************
- // * DoIdleProc
- // *
- // * this routine is called each time through our event loop. We
- // * process any adsp errors that were returned and check for connections
- // * coming and going.
- // *****************************************************************
- void DoIdleProc()
- {
- ADSPLoop();
- }
-
- // *****************************************************************
- // * AdjustCursor
- // *
- // *Change the cursor's shape, depending on its position. This also calculates the region
- // * where the current cursor resides (for WaitNextEvent). If the mouse is ever outside of
- // * that region, an event would be generated, causing this routine to be called,
- // * allowing us to change the region to the region the mouse is currently in. If
- // * there is more to the event than just “the mouse moved”, we get called before the
- // * event is processed to make sure the cursor is the right one. In any (ahem) event,
- // * this is called again before we fall back into WNE.
- // *****************************************************************
- void AdjustCursor (Point mouse, RgnHandle region)
- {
- WindowPtr window;
- RgnHandle arrowRgn;
- RgnHandle ourRgn;
- Rect globalPortRect;
-
- Rect r;
- short kind;
- Handle h;
-
- window = FrontWindow(); /*we only adjust the cursor when we are in front*/
- if ((!gInBackground) && (!IsDAWindow(window)))
- {
- /*calculate regions for different cursor shapes*/
- arrowRgn = NewRgn();
- ourRgn = NewRgn();
-
- /*start with a big, big rectangular region*/
- SetRectRgn(arrowRgn, extremeNeg, extremeNeg, extremePos, extremePos);
-
- /*calculate ourRgn*/
- if (IsAppWindow(window))
- {
- SetPort(window); /*make a global version of the portRect*/
- SetOrigin(-window->portBits.bounds.left, -window->portBits.bounds.top);
- globalPortRect = window->portRect;
- RectRgn(ourRgn, &globalPortRect);
- SectRgn(ourRgn, window->visRgn, ourRgn);
- SetOrigin(0, 0);
- }
-
- /*subtract other regions from arrowRgn*/
- DiffRgn(arrowRgn, ourRgn, arrowRgn);
-
- /*change the cursor and the region parameter*/
- if (PtInRgn(mouse, ourRgn))
- {
- GetDItem(myDialog, kOutgoingTextID, &kind, &h, &r);
- GlobalToLocal(&mouse);
- if (PtInRect(mouse, &r))
- SetCursor(*GetCursor(iBeamCursor));
- else
- SetCursor(&qd.arrow);
- CopyRgn(ourRgn, region);
- }
- else
- {
-
- SetCursor(&qd.arrow);
- CopyRgn(arrowRgn, region);
-
- }
-
- /*get rid of our local regions*/
- DisposeRgn(arrowRgn);
- DisposeRgn(ourRgn);
- }
- } /*AdjustCursor*/
-
- // *****************************************************************
- // * UpdateItemBorder
- // *
- // * re-draws the borders around our items
- // *****************************************************************
- void UpdateItemBorder (short item, Rect r)
- {
- FontInfo fInfo;
- Rect tRect;
- Str255 theBorderString;
-
- switch(item)
- {
- case kRemoteMacsTimeBorderID:
- strcpy(&theBorderString,"Time from remote Mac");
- break;
- case kIncomingMessageBorderID:
- strcpy(&theBorderString,"Incoming message");
- break;
- case kPopupBorderID:
- strcpy(&theBorderString,"Select A Target Machine");
- break;
- case kOutgoingMessageBorderID:
- strcpy(&theBorderString,"Outgoing message");
- break;
- case kConnectStatusBorder:
- strcpy(&theBorderString,"Connection Status");
- break;
-
- default:
- break;
- }
-
- c2pstr(theBorderString);
-
- GetFontInfo(&fInfo);
- FrameRect(&r);
- MoveTo(r.left + 5, r.top + fInfo.ascent / 2 - 1);
- tRect.left = r.left + 4;
- tRect.right = tRect.left + StringWidth(theBorderString) + 1;
- tRect.top = r.top;
- tRect.bottom = r.top + 1;
- EraseRect(&tRect);
- DrawString(&theBorderString);
-
- }
-
- // *****************************************************************
- // * PlotSICN
- // *
- // * this is the PlotSICN code stolen from Tech Note #
- // *****************************************************************
- void PlotSICN (Rect theRect,SICNHand theSICN, short theIndex)
- {
-
- SignedByte state; /* we want a chance to restore original state */
- BitMap srcBits; /* built up around 'SICN' data so we can _CopyBits */
-
- /* check the index for a valid value */
- if ((GetHandleSize((Handle)theSICN) / sizeof(SICN)) > theIndex)
- {
-
- /* store the resource's current locked/unlocked condition */
- state = HGetState((Handle)theSICN);
-
- /* lock the resource so it won't move during the _CopyBits call */
- HLock((Handle)theSICN);
-
- /* set up the small icon's bitmap */
- /*$PUSH*/
- /*$R-*/
- /* turn off range checking */
- srcBits.baseAddr = (Ptr)(&(**theSICN[theIndex]));
- /*$POP*/
- srcBits.rowBytes = 2;
- SetRect(&srcBits.bounds, 0, 0, 16, 16);
-
- /* draw the small icon in the current grafport */
- CopyBits(&srcBits, &qd.thePort->portBits, &srcBits.bounds, &theRect, srcCopy, nil);
-
- /* restore the resource's locked/unlocked condition */
- HSetState((Handle)theSICN, state);
- }
-
- }
-
- // *****************************************************************
- // * drawPopUpTri
- // *
- // * this procedure draws the new "standard" SICN triangle now used
- // * in popup menus I guess the drop shadow was not enough of an
- // * indiciation to the users of the presence of the pop-up.
- // * standard in 7.0 and up systems
- // *****************************************************************
- void drawPopUpTri (WindowPtr whichWindow, Rect r)
- {
-
- #pragma unused (whichWindow)
-
- Handle popUpTri;
- Rect popUpTriRect;
-
- popUpTri = GetResource('SICN', kStandardTriSICN);
- if (popUpTri)
- {
- popUpTriRect = r;
- popUpTriRect.right = popUpTriRect.right - 1;
- popUpTriRect.left = popUpTriRect.right - 16;
- popUpTriRect.top = popUpTriRect.top + 1;
- popUpTriRect.bottom = popUpTriRect.top + 16;
- PlotSICN(popUpTriRect, (SICNHand)popUpTri, 0);
- ReleaseResource(popUpTri);
- }
-
-
- }
-
- // *****************************************************************
- // * DoEvent
- // *
- // * Do the right thing for an event. Determine what kind of event it is, and call
- // * the appropriate routines.
- // *****************************************************************
- void DoEvent (EventRecord event)
- {
- short part;
- char key;
- WindowPtr whichWindow;
- DialogPeek dp;
- short teLength;
- DSPPBPtr dspPBPtr;
-
-
- whichWindow = FrontWindow();
-
- switch(event.what)
- {
- case nullEvent:
- break;
- case mouseDown:
- part = FindWindow(event.where, &whichWindow);
- if (part != 0)
- {
- switch(part)
- {
- case inMenuBar:
- /*process the menu command*/
- AdjustMenus();
- DoMenuCommand(MenuSelect(event.where));
- break;
- case inSysWindow: /*let the system handle the mouseDown*/
- SystemClick(&event, whichWindow);
- break;
-
- case inContent:
- if (whichWindow != FrontWindow())
- SelectWindow(whichWindow);
- break;
-
- case inDrag: /*pass screenBits.bounds to get all gDevices*/
- DragWindow(whichWindow, event.where, &qd.screenBits.bounds);
- break;
-
- case inGrow:
- break;
- case inZoomIn:
- case inZoomOut:
- break;
- }
- }
- break;
- case keyDown:
- case autoKey:
- /*check for menukey equivalents*/
- key = (char)(event.message & charCodeMask);
- if ((event.modifiers & cmdKey) != 0) /*Command key down*/
- {
- if ((event.what == keyDown) || (event.what == autoKey))
- {
- AdjustMenus(); /*enable/disable/check menu items properly*/
- DoMenuCommand(MenuKey(key));
- }
- }
- else if (key == (char)kEnterKey) /* enter key */
- {
- if ( (gMyCCB.state == sClosed) ||
- (gMyCCB.state == sPassive))
- ShowError(noConnErr);
- else
- {
- dp = (DialogPeek)myDialog;
-
- /* we'll take a maximum of 255 characters from the edit box */
- teLength = ((**(*dp).textH).teLength < 255) ? (**(*dp).textH).teLength : 255;
-
- /* grab the text from our edit text box */
- BlockMove( *((**(*dp).textH).hText), outgoingDataBuffer, teLength);
-
- /* we'll make sure we get a parameter block
- so we can send our data */
- do
- {
- /* get QElement for the write call */
- dspPBPtr = GetQElement(&gAvailQueue);
- }
- while ( (dspPBPtr == NULL) );
-
- writeOutgoing(dspPBPtr,
- gCCBRefNum,
- outgoingDataBuffer,
- teLength);
-
- /* Change selection to outgoing text TERecord */
- SelIText(myDialog, kOutgoingTextID, 0, 32767);
-
- }
-
- }
- break; /*call DoActivate with the window and...*/
- case activateEvt: /*true for activate, false for deactivate*/
- DoActivate((WindowPtr)event.message, (event.modifiers & activeFlag) != 0);
- break;
- case updateEvt:
- break;
- case osEvent:
- switch(event.message >> 24) /*high byte of message*/
- {
- case suspendResumeMessage:
- gInBackground = (event.message & resumeMask) == 0;
- DoActivate(FrontWindow(), !gInBackground);
- break;
- }
-
- }
- } /*DoEvent*/
-
- // *****************************************************************
- // * EventLoop
- // *
- // * Get events forever, and handle them by calling DoEvent.
- // * Get the events by calling WaitNextEvent, if it's available, otherwise
- // * by calling GetNextEvent. Also call AdjustCursor each time through the loop.
- // *****************************************************************
- void EventLoop()
- {
- RgnHandle cursorRgn;
- Boolean gotEvent;
- EventRecord event;
- long sleepTime;
- WindowPtr whichDialog;
- short whichItem;
-
-
- cursorRgn = NewRgn(); /*we’ll pass WNE an empty region the 1st time thru*/
- sleepTime = 2;
- do
- {
- if (gHasWaitNextEvent) /*put us 'asleep' forever under MultiFinder*/
- {
- gotEvent = WaitNextEvent(everyEvent, &event, sleepTime, cursorRgn);
- }
- else
- {
- SystemTask(); /*must be called if using GetNextEvent*/
- gotEvent = GetNextEvent(everyEvent, &event);
- }
-
- DoIdleProc();
- AdjustCursor(event.where, cursorRgn); /*make sure we have the right cursor*/
- whichDialog = FrontWindow();
-
- /* don't pass command keys or <enter> keys to our dialog */
- if (!((event.what==keyDown)&&(event.modifiers & cmdKey))
- && (IsDialogEvent(&event))
- && !((event.what==keyDown)&&((event.message & charCodeMask) == (char)kEnterKey)))
- {
- if (DialogSelect(&event, &whichDialog, &whichItem))
- DoModeless(whichDialog, whichItem);
- }
- else
- DoEvent(event);
-
- }
- while (true); /*loop forever; we quit through an ExitToShell*/
- }
-
-
-
- // *****************************************************************
- // * TrapAvailable
- // *
- // * Check to see if a given trap is implemented. This is only used by the
- // * Initialize routine in this program, so we put it in the Initialize segment.
- // * The recommended approach to see if a trap is implemented is to see if
- // * the address of the trap routine is the same as the address of the
- // * Unimplemented trap.
- // *****************************************************************
- #pragma segment Initialize
- Boolean TrapAvailable(tNumber,tType)
- short tNumber;
- TrapType tType;
- {
- if ( ( tType == ToolTrap ) &&
- ( gMac.machineType > envMachUnknown ) &&
- ( gMac.machineType < envMacII ) )
- { /* it's a 512KE, Plus, or SE */
- tNumber = tNumber & 0x03FF;
- if ( tNumber > 0x01FF ) /* which means the tool traps */
- tNumber = _Unimplemented; /* only go to 0x01FF */
- }
- return NGetTrapAddress(tNumber, tType) != GetTrapAddress(_Unimplemented);
- } /*TrapAvailable*/
-
- // *****************************************************************
- // * zeroOutStrings
- // *
- // * clears out the name, time and incoming text strings
- // *****************************************************************
- void zeroOutStrings()
- {
- /* this procedure emptys all connection oriented strings in the main dialog */
-
- Rect r;
- short kind;
- Handle h;
-
- GetDItem(myDialog, kRemoteMacsNameID, &kind, &h, &r);
- SetIText(h, "\p");
- GetDItem(myDialog, kRemoteMacsTimeID, &kind, &h, &r);
- SetIText(h, "\p");
- GetDItem(myDialog, kIncomingTextID, &kind, &h, &r);
- SetIText(h, "\p");
- }
-
- // *****************************************************************
- // * SetupUserItems
- // *
- // *****************************************************************
- void SetupUserItems()
- {
- setEachUserItem(kzoneItemID);
- setEachUserItem(ktypeItemID);
- setEachUserItem(kobjectItemID);
- setEachUserItem(kRemoteMacsTimeBorderID);
- setEachUserItem(kIncomingMessageBorderID);
- setEachUserItem(kConnectStatusBorder);
- setEachUserItem(kPopupBorderID);
-
- /* set connect button to unhilited */
- HiliteConnectButton(255);
- }
-
-
- // *****************************************************************
- // * Initialize
- // *
- // * program initialization
- // *****************************************************************
- void Initialize()
- {
-
- Rect r;
- short kind;
- Handle h;
- Handle menuBar;
- DialogPeek dp;
-
- gInBackground = false;
-
- InitGraf(&qd.thePort);
- InitFonts();
- InitWindows();
- InitMenus();
- TEInit();
- InitDialogs(nil);
- InitCursor();
-
-
- if (InitAppleTalk() != noErr)
- Exit(atalkErr);
-
- gZoneString[0] = 0;gTypeStr[0] = 0;gObjStr[0] = 0;
-
- GetOurZone();
-
- /* we will allocate our own window storage instead of letting the Window */
- /* Manager do it because GetNewWindow may load in temp. resources before */
- /* making the NewPtr call, and this can lead to heap fragmentation. */
- myDialog = (DialogPtr)(NewPtr(sizeof(DialogRecord)));
- if (myDialog == nil)
- Exit(memErr);
-
-
- myDialog = GetNewDialog(rDialog, (Ptr)myDialog, (DialogPtr)-1);
-
- SetPort(myDialog);
-
- dp = (DialogPeek)myDialog;
-
- TextFont(geneva);
- TextSize(9);
-
- (**(dp->textH)).txFont = geneva;
- (**(dp->textH)).txSize = 9;
-
- SetWTitle(myDialog, "\pADSP");
-
- ShowWindow(myDialog);
-
- LastZoneMenuChoice = 0;
- LastTypeMenuChoice = 0;
- LastObjectMenuChoice = 0;
-
- SetupUserItems();
- /* show blinking cursor in outgoing text box */
- SelIText(myDialog, kOutgoingTextID, 0, 32767);
-
- /* turn on "Moof" entity filter (check box) initially */
- GetDItem(myDialog, kMoofFilterCheckBox, &kind, &h, &r);
- SetCtlValue((ControlHandle)h,1);
- gMoofEntityFilter = true;
- CopyPstr("\pMoof", gTypeStr);
- gObjStr[0] = 0;
- HiliteConnectButton(0);
-
-
- menuBar = GetNewMBar(rMenuBar); /*read menus into menu bar*/
- if (menuBar == nil)
- Exit(menuErr);
- SetMenuBar(menuBar); /*install menus*/
- DisposHandle(menuBar);
- AddResMenu(GetMHandle(mApple), 'DRVR'); /*add DA names to Apple menu*/
- DrawMenuBar();
-
- gStopped = true;
- zeroOutStrings();
-
- initializeADSP();
-
- } /*Initialize*/
-
- // *****************************************************************
- // * CheckEnvirons
- // *
- // * check the current operating environment
- // *****************************************************************
- void CheckEnvirons()
- {
- long total, contig, response;
- OSErr ignoreError;
-
-
- /* ignore the error returned from SysEnvirons; even if an error occurred,*/
- /* the SysEnvirons glue will fill in the SysEnvRec*/
- ignoreError = SysEnvirons(sysEnvironsVersion, &gMac);
-
- /* Make sure that the machine has at least 128K ROMs. If it doesn't, exit. */
- if (gMac.machineType < 0) FatalError(9);
- if ((long) GetApplLimit() - (long) ApplicZone() < kMinHeap) FatalError(10);
- PurgeSpace(&total, &contig);
- if (total < kMinSpace)
- if (UnloadScrap() != noErr)
- FatalError(11);
- else
- {
- PurgeSpace(&total, &contig);
- if (total < kMinSpace)
- FatalError(11);
- }
-
- /* verify if WaitNextEvent, Gestalt and PPCToolbox are available */
- gHasWaitNextEvent = TrapAvailable(_WaitNextEvent, ToolTrap);
- if (TrapAvailable(_Gestalt, ToolTrap))
- { /* verify if system 7.0 */
- Gestalt(gestaltSystemVersion,&response );
- if (response >= 0x0700)
- gHasSystem7 = true;
- else gHasSystem7 = false;
- }
- else
- {
- SysBeep(20);
- gHasSystem7 = false;
- }
-
- }
-
-
- // *****************************************************************
- // * Main
- // *
- // *****************************************************************
- #pragma segment Main
- main()
- {
- MaxApplZone(); /*expand the heap so code segments load at the top*/
- CheckEnvirons(); /*check for some basic requirements; exits if not met*/
- Initialize(); /*initialize the program*/
- UnloadSeg(&Initialize); /*note that Initialize must not be in Main!*/
- EventLoop(); /*call the main event loop*/
-
- }